package common

import (
	"fmt"
	//	"io/ioutil"
	//"net"
	//"net/http"
	"time"
)

type Action func()
type Getter func(string, map[string][]string) (string, error)
type Checker func() bool

type WorkShop struct {
	BaseUrl       string
	Interval      int
	Jobs          []Job
	stopping      chan struct{}
	stopped       chan struct{}
	ExitAction    Action
	RestartAction Action
	Info          string
}

func (w *WorkShop) performAction() {
	acted := false
	for _, job := range w.Jobs {
		if job.ShouldExit() && w.ExitAction != nil && !acted {
			w.ExitAction()
			w.ExitAction = nil //release hook
			acted = true
		} else if job.ShouldRestart() && w.RestartAction != nil && !acted {
			w.RestartAction()
			w.RestartAction = nil //release hook
			acted = true
		}
	}
}

func (w *WorkShop) Start() {
	w.stopped = make(chan struct{})
	w.stopping = make(chan struct{})
	for _, job := range w.Jobs {
		job.OnStart(w.BaseUrl, w.Info)
	}
}

func (w *WorkShop) getParams() map[string]string {
	//pull from http
	//TODO
	return nil
}

func (w *WorkShop) Run() {
	ticker := time.NewTicker(time.Duration(w.Interval) * time.Second)
	for {
		w.performAction()
		select {
		case <-ticker.C:
			for _, job := range w.Jobs {
				if job.Started() {
					job.OnTick(w.BaseUrl, w.getParams())
				}
			}
		case <-w.stopping:
			ticker.Stop()
			for _, job := range w.Jobs {
				if job.Started() {
					job.OnStop(w.BaseUrl)
				}
			}
			close(w.stopped)
			return
		}
	}
}

func (w *WorkShop) Stop() error {
	close(w.stopping)
	<-w.stopped
	for _, job := range w.Jobs {
		if job.Started() {
			return fmt.Errorf("stop error:job:%s", job)
		}
	}
	return nil
}

//heart beat job
//use Checker to determine outside task successed
